package router

import (
	"context"
	"errors"
	"fmt"
	"go-proxy/api"
	"go-proxy/initialize"
	_ "go-proxy/initialize"
	"net/http"
	"os"
	"os/signal"
	"time"

	"github.com/gin-gonic/gin"
	"go.uber.org/zap"
)

func Run() {

	router := gin.New()
	gin.SetMode(initialize.Config.Server.Model)

	gin.DebugPrintRouteFunc = func(httpMethod, absolutePath, handlerName string, nuHandlers int) {
		initialize.Logger.Info("路由",
			zap.String("method", httpMethod),
			zap.String("path", absolutePath),
		)
	}

	router.Use(LoggerMiddle(initialize.Logger)).
		Use(RecoveryMiddle(initialize.Logger, true)).
		Use(CorsMiddle())

	root := router.Group(initialize.Config.Server.ContextPath)
	api.RegisterSystemController(root)

	server := &http.Server{
		Addr:         fmt.Sprintf(":%d", initialize.Config.Server.Port),
		Handler:      router,
		ReadTimeout:  30 * time.Second,
		WriteTimeout: 30 * time.Second,
	}

	initialize.Logger.Info("服务器启动", zap.Int("port", initialize.Config.Server.Port))

	go func() {
		if err := server.ListenAndServe(); err != nil && !errors.Is(err, http.ErrServerClosed) {
			initialize.Logger.Error("启动服务失败", zap.String("error", err.Error()))
		}
	}()

	// 等待中断信号以优雅地关闭服务器（设置 5 秒的超时时间）
	quit := make(chan os.Signal)
	signal.Notify(quit, os.Interrupt)
	<-quit
	initialize.Logger.Info("服务正在停止")

	ctx, cancel := context.WithTimeout(context.Background(), 5*time.Second)
	defer cancel()
	if err := server.Shutdown(ctx); err != nil {
		initialize.Logger.Error("服务停止失败", zap.String("error", err.Error()))
	}
	initialize.Logger.Info("服务停止")
}
